package com.dq.controller.api.user;
import com.alibaba.fastjson.JSONObject;
import com.dq.domain.sys.user.user.BossUser;
import com.dq.exception.customException.AdminException;
import com.dq.controller.in.request.FeedbackAdd;
import com.dq.vo.Vo;
import com.dq.domain.subscribe.Subscribe;
import com.dq.vo.baseVo.VO;
import com.dq.domain.evaluation.EvaluationRecord;
import com.dq.domain.evaluation.EvaluationRecordTemplate;
import com.dq.domain.evaluation.EvaluationTemplate;
import com.dq.domain.evaluation.EvaluationTemplateChild;
import com.dq.domain.record.ServiceRecord;
import com.dq.domain.service.ServiceProjectRecordCentre;
import com.dq.domain.sys.user.user.base.SysUser;
import com.dq.domain.sys.user.user.WxUser;
import com.dq.service.AllService;
import com.dq.utils.FileUtil;
import com.dq.utils.PageableUtil;
import com.dq.utils.SmallQrCode;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.http.HttpStatus;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.io.IOException;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.*;


/**
 * @author liuhui
 * @date 2019/9/16 0016 17:46:28
 */
@Api(description = "用户管理")
@RestController
@RequestMapping("/api/user")
public class ApiUserInfoController extends AllService {
    @Value("${oss-show-url}")
    private String url;
    @Value("${score_sum}")
    private Long scoreSum;

    @ApiOperation("顾客详细信息, 包括会员卡集合")
    @GetMapping("/myinfo")
    public Vo findMyInfo()throws AdminException{
        SysUser sysUser = sysUserService.getUser();
        if(!(sysUser instanceof WxUser)) {
            throw new AdminException("登录账号非微信用户");
        }
        WxUser loginUser = (WxUser) sysUser;
        WxUser.FrontWxUser frontWxUser = loginUser.toFrontWxUser();
        frontWxUser.setLableStrList(wxUserService.getWxUserLable(loginUser));
        frontWxUser.setUserCardList(wxUserService.getWxUserCardList(loginUser, null));

        return new Vo(frontWxUser);
    }

    @ApiOperation("上传用户头像")
    @PostMapping("/upload/userImg")
    public Vo headUpload(@ApiParam(value = "用户头像") MultipartFile file) throws IOException, AdminException {
        SysUser sysUser = shiroService.getUser();
        if(null==sysUser){
            throw new AdminException("您还未登陆");
        }
        WxUser wxUser = dao.get(WxUser.class,sysUser.getId());
        if(null==file ||file.getSize()<1){
            throw new AdminException("请上传头像");
        }
        String fileName = ossService.upload(FileUtil.save(file));
        wxUser.setHeadImg(url+fileName);
        wxUserRepository.save(wxUser);
        return new Vo(url+fileName);
    }

    @ApiOperation("生成小程序推广二维码,返回base64String")
    @GetMapping("/generate/small")
    public Object generateSmall(String phone,String width){
        String accessToken = SmallQrCode.getAccessToken();
        String base64Code = SmallQrCode.getWXQrcode(accessToken,"pages/index/index",""+phone,Integer.parseInt(width));
        JSONObject jsonObject = new JSONObject();
        jsonObject.put("code","200");
        jsonObject.put("imgUrl",base64Code);
        return jsonObject;
    }

    @ApiOperation("反馈列表")
    @GetMapping("/feedback")
    public Vo feedback () throws AdminException{
        EvaluationTemplate paren = dao.get(EvaluationTemplate.class,1L);
        List<EvaluationTemplate> evaluationTemplates = evaluationTemplateRepository.findByDeletedFalseAndParentOrderBySortAsc(paren);
        List<EvaluationTemplate.EvaluationTemplateVo> evaluationTemplateVos = new ArrayList<>();
        evaluationTemplates.forEach(evaluationTemplate -> {
            evaluationTemplateVos.add(evaluationTemplate.toEvaluationTemplateVo());
        });
        evaluationTemplateVos.forEach(evaluationTemplateVo -> {
            EvaluationTemplate evaluationTemplate = dao.get(EvaluationTemplate.class,evaluationTemplateVo.getId());
            List<EvaluationTemplateChild.EvaluationTemplateChildList> lists = new ArrayList<>();
            List<EvaluationTemplateChild> children = evaluationTemplateChildRepository.findByEvaluationTemplateAndDeletedFalseOrderBySortAsc(evaluationTemplate);
            children.forEach(evaluationTemplateChild -> {
                lists.add(evaluationTemplateChild.toEvaluationTemplateChildList());
            });
            evaluationTemplateVo.setChildren(lists);
        });
        return new Vo(evaluationTemplateVos);
    }

    @ApiOperation("提交评价")
    @PostMapping("addFeedback")
    @Transactional(rollbackFor = Exception.class)
    public Vo addFeedback (@RequestBody FeedbackAdd feedbackAdd) throws AdminException{
        List<Long> longs = feedbackAdd.getChilds();
        if(longs.size() == 0){
            throw new AdminException("请先评分");
        }
        Subscribe subscribe = dao.get(Subscribe.class,feedbackAdd.getSubscribeId());
        if(subscribe == null){
            throw new AdminException("此预约不存在");
        }
        EvaluationRecord er = new EvaluationRecord();
        er.setContent(feedbackAdd.getContent());
        er.setSubscribe(subscribe);
        Long sum = 0L;
        for(Long l : feedbackAdd.getChilds()){
            EvaluationTemplateChild evaluationTemplateChild = dao.get(EvaluationTemplateChild.class,l);
            sum+=evaluationTemplateChild.getScore();
        }
        int count = feedbackAdd.getChilds().size();
        Long averageScore =sum/count;
        BigDecimal scoringScale = new BigDecimal(sum).divide(new BigDecimal(scoreSum),2, RoundingMode.HALF_UP);
        er.setAverageScore(averageScore);
        EvaluationRecord evaluationRecord= evaluationRecordRepository.save(er);

        List<EvaluationRecordTemplate> evs = new ArrayList<>();
        for (Long l:longs) {
            EvaluationRecordTemplate ev = new EvaluationRecordTemplate();
            ev.setEvaluationRecord(evaluationRecord);
            EvaluationTemplateChild evaluationTemplateChild = dao.get(EvaluationTemplateChild.class,l);
            ev.setEvaluationTemplateChild(evaluationTemplateChild);
            ev.setEvaluationTemplate(evaluationTemplateChild.getEvaluationTemplate());
            evs.add(ev);
        }
        evaluationRecordTemplateRepository.saveAll(evs);
        subscribe.setSubscribeStatus(Subscribe.SubscribeStatus.serviced);
        subscribeRepository.save(subscribe);
        //计算手工费 存入服务记录  调整服务费计算规则为：服务费乘以员工评分
//        serviceRecordService.addManualPrice(feedbackAdd.getServiceRecordId(),scoringScale);
        BossUser bossUser = subscribe.getTechnicianUser();
        if(bossUser.getNum() == null) {
            bossUser.setNum(1L);
        }else {
            bossUser.setNum(bossUser.getNum()+1L);
        }

        BigDecimal averageScoreSum = (bossUser.getAverageScore().multiply(new BigDecimal(bossUser.getNum()))).add(new BigDecimal(averageScore));
        bossUser.setAverageScore(averageScoreSum.divide(new BigDecimal(bossUser.getNum()),1, RoundingMode.HALF_UP));
        bossUserRepository.save(bossUser);
        return new Vo(HttpStatus.OK);
    }

    @GetMapping("/evaluateDetail/{evaluateId}")
    @ApiOperation("反馈详情")
    public Vo evaluateDetail(@PathVariable Long evaluateId)throws AdminException{
        EvaluationRecord evaluationRecord = dao.get(EvaluationRecord.class,evaluateId);
        if(!Optional.ofNullable(evaluationRecord).isPresent()){throw new AdminException("评价记录不存在");}
        List<EvaluationRecordTemplate> evaluationRecordTemplateList = evaluationRecordTemplateRepository.findByEvaluationRecord(evaluationRecord);
        return new Vo(evaluationRecord.toOrgEvaluationDetailVo((List<EvaluationRecordTemplate.Vo>) VO.toVOCollection(evaluationRecordTemplateList)));
    }

    @ApiOperation("我的服务记录列表")
    @PostMapping("/myServiceRecord/{page}/{size}")
    public Vo myServiceRecord (@PathVariable @ApiParam("页数") Integer page,
                               @PathVariable @ApiParam("页长") Integer size) throws AdminException{
        SysUser user = shiroService.getUser();
        if(null==user){
            throw new AdminException("您还未登陆");
        }
        List<ServiceRecord> serviceRecords = serviceRecordRepository.findByWxUserAndServiceStatusAndDeletedFalseOrderByCreateTimeDesc(user, ServiceRecord.ServiceStatus.endService,PageableUtil.get(page, size)).getContent();
        Long total = serviceRecordRepository.countByWxUserAndServiceStatusAndDeletedFalse(user, ServiceRecord.ServiceStatus.endService);
        HashMap<String,Object> map = new HashMap<>();
        //预约次数
        Long subscribeNum = subscribeRepository.countBySubscribeStatusAndDeletedFalseAndWxUser(Subscribe.SubscribeStatus.serviced,user);
        //服务次数
        Long serviceNum = serviceRecordRepository.countByWxUserAndServiceStatus(user, ServiceRecord.ServiceStatus.endService);
        List<ServiceRecord.UserServiceRecord> list = new ArrayList<>();
        List<String> strings = new ArrayList<>();
        for (ServiceRecord serviceRecord:serviceRecords) {
            boolean flag = false;
            Long evaluateId = null;
//            EvaluationRecord record = evaluationRecordRepository.findByServiceRecordAndDeletedFalse(serviceRecord);
            EvaluationRecord record = null;
            if(record != null){
                flag = true;
                evaluateId = record.getId();
            }
            List<ServiceProjectRecordCentre> s = serviceProjectRecordCentreRepository.findByServiceRecord(serviceRecord);
            s.forEach(n ->{
                strings.add(n.getServiceProject().getProjectName());
            });
            list.add(serviceRecord.toUserServiceRecord(flag,strings,evaluateId));
        }
        map.put("record",list);
        map.put("subscribeNum",subscribeNum);
        map.put("serviceNum",serviceNum);
        map.put("total_count",total);
        return new Vo(map);
    }

}
